home *** CD-ROM | disk | FTP | other *** search
- /* NoDirCache.c use hdwrench.library to change a partition from DirCache to
- * something safe.
- * $VER: NoDirCache.c 44.1(22.9.2000) © Wizardess Designs and Joanne Dow 1999 All rights reserved
- *
- * © Copyright 1999 by Joanne Dow, Wizardess Designs
- * All Rights Reserved
- *
- * Presumes "scsi.device" else enter "DEVICE devicename".
- */
- #include <stdio.h>
- #include <stdarg.h>
- #include <string.h>
- #include <ctype.h>
- #include <stdlib.h>
- #include <math.h>
- #include <dos.h>
- #include <exec/types.h>
- #include <exec/ports.h>
- #include <exec/libraries.h>
- #include <exec/io.h>
- #include <exec/nodes.h>
- #include <exec/lists.h>
- #include <exec/tasks.h>
- #include <exec/memory.h>
- #include <exec/execbase.h>
- #include <devices/trackdisk.h>
- #include <libraries/dos.h>
- #include <libraries/dosextens.h>
- #include <dos/filehandler.h>
- #include <devices/hardblocks.h>
- #include <devices/scsidisk.h>
- #include <intuition/intuition.h>
- #include <workbench/workbench.h>
- #include <workbench/icon.h>
- #include <workbench/startup.h>
- #include <dos/rdargs.h>
- #include <dos/dostags.h>
-
- #include <proto/dos.h>
- #include <proto/exec.h>
- #include <pragmas/exec_pragmas.h>
- #include <pragmas/disk_pragmas.h>
- #include <pragmas/dos_pragmas.h>
-
- #include "HDWrench.h"
- #include "HDWrench_pragmas.h"
- #define USE_SUGGESTED_MESSAGES
-
- struct HDWLibrary *HDWBase = NULL;
-
- #define TEMPLATE "TYPE/K/A,DEVICE/K,UNIT/N/K/A,FILE/K/A"
- #define NUM_ARGS 4
- #define FFS 0x444f5301
- #define FFS_INTL 0x444f5303
- #define DIRCACHE 0x444f5305
- #define DIRCACHEI 0x444f5307
-
- char hexits [] = "0123456789abcdef";
- char spaces [] = " ";
-
- enum { ARG_TYPE, ARG_DEVICE, ARG_UNIT, ARG_FILE };
-
- LONG ArgArray [ NUM_ARGS ];
-
- char* membuffer = NULL;
- BOOL deviceopen = FALSE;
- struct RDArgs* Args = NULL;
- BOOL aborted = FALSE;
- ULONG testnum;
-
- typedef union smallbootblock
- {
- UBYTE bd_Bytes[512]; // NB: This is the MINIMUM size we
- UWORD bd_Words[256]; // can have here. It MAY be extended
- ULONG bd_Longs[128]; // if ddBlockBytes is larger.
- struct RigidDiskBlock bd_RDB;
- struct BadBlockBlock bd_BB;
- struct PartitionBlock bd_PB;
- struct FileSysHeaderBlock bd_FHB;
- struct LoadSegBlock bd_LSB;
- } SmallBootBlock;
-
- #define sbb_Bytes sbb_Data->bd_Bytes
- #define sbb_Words sbb_Data->bd_Words
- #define sbb_Longs sbb_Data->bd_Longs
- #define sbb_RDB sbb_Data->bd_RDB
- #define sbb_BB sbb_Data->bd_BB
- #define sbb_PB sbb_Data->bd_PB
- #define sbb_FHB sbb_Data->bd_FHB
- #define sbb_LSB sbb_Data->bd_LSB
- #define sbb_ID sbb_Data->bd_Longs [ 0 ]
- #define sbb_Next sbb_Data->bd_Longs [ 4 ]
- #define sbb_Check sbb_Data->bd_Longs [ 2 ]
-
- BOOL handlePartition ( SmallBootBlock* sbb_Data, ULONG newDosType, ULONG blocksize );
- void usage ( void );
- int btrap ( void );
- void gone ( void );
-
- int
- main ( int argc, char **argv)
- {
- char* filename;
- char devicename[60];
- ULONG baseunit;
- ULONG ffstype;
- ULONG sizememneeded;
-
- ULONG rsuccess;
- USHORT rwsuccess;
-
- ArgArray [ 0 ] =
- ArgArray [ 1 ] =
- ArgArray [ 2 ] =
- ArgArray [ 3 ] = 0 ;
-
- puts( "NoDirCache - Switch DirCache partitions to \"FFS\" or \"FFS_INTL\".\n" );
-
- atexit( gone );
- if ( onbreak ( &btrap ))
- {
- printf ( "Break trap not installed!" );
- exit ( 20 );
- }
-
- Args = ReadArgs( TEMPLATE, ArgArray, NULL );
- if ( Args )
- {
- // ARG_TYPE, ARG_DEVICE, ARG_UNIT, ARG_FILE
- memset ( devicename, 0, 60 );
- if ( ArgArray [ ARG_TYPE ] != NULL )
- {
- if ( stricmp( (char*) ArgArray [ ARG_TYPE ], "FFS" ) == 0 )
- ffstype = 0x444f5301L;
- else
- if ( stricmp( (char*) ArgArray [ ARG_TYPE ], "FFS_INTL" ) == 0 )
- ffstype = 0x444f5303L;
- else
- {
- usage();
- exit( 20 );
- }
- }
-
- if ( ArgArray [ ARG_DEVICE ] != NULL )
- strncpy ( devicename, (char *) ArgArray [ ARG_DEVICE ], 59 );
- else
- {
- usage();
- exit( 20 );
- }
-
- baseunit = *(ULONG *) ArgArray [ ARG_UNIT ];
-
- filename = (char *) ArgArray [ ARG_FILE ];
-
- printf ( "Type = 0x%lx\n", ffstype );
- printf ( "Unit = %ld\n", baseunit );
- printf ( "Filename = %s\n", filename );
- printf ( "Devicename = %s\n\n\n", devicename);
-
- if ( strlen( filename ) > 248 )
- {
- printf ( "Filename: %s is too long!\n", filename );
- exit( 10 );
- }
-
- if (( HDWBase = ( struct HDWLibrary *) OpenLibrary ( HDWBaseName, 0)) == NULL )
- {
- printf ( "Failed to open HDWBase!\n");
- exit ( 20 );
- }
- }
- else
- {
- usage ();
- exit ( 20 );
- }
-
- // All setup and places to go. Let's read in the RDBs since we need them
- // for a lot of things. If we place them in memory we can parse them easier.
- // Let's use the raw RDBs because they are in handy structure format for
- // reading.
-
- printf ( "Attempting to open: %s:%d\n", devicename, baseunit );
- deviceopen = HDWOpenDevice ( devicename, baseunit );
- if ( !deviceopen )
- {
- printf ( "No device was opened!\n");
- exit ( 20 );
- }
- printf ( "Attempting to read RDBs into library.\n");
-
- rwsuccess = ReadRDBs ( );
-
- if ( rwsuccess == success )
- {
- sizememneeded = 0;
- rsuccess = OutMemRDBStructs ( NULL, &sizememneeded, 0 );
-
- if ( rsuccess == E_NOERROR )
- {
- printf ( "Need %ld bytes of buffer for mountfile.\n", sizememneeded );
- membuffer = malloc ( sizememneeded );
- if ( membuffer )
- {
- rsuccess = OutMemRDBStructs ( membuffer, &sizememneeded, sizememneeded );
- if ( rsuccess == E_NOERROR )
- {
- // Now we have things in memory. We can do something
- // with it all.
- // generate pointer to base block.
- SmallBootBlock* sbb_Data = (SmallBootBlock*) &membuffer[0];
- ULONG blocksize = sbb_RDB.rdb_BlockBytes;
- ULONG offset = sbb_RDB.rdb_RDBBlocksLo;
- if ( offset > 16L )
- {
- printf ( "Illegal RDB start block found: %ld\n", offset );
- exit ( 20 );
- }
- // Generate physical block size
- if (( blocksize != 512L )
- && ( blocksize != 1024L )
- && ( blocksize != 2048L )
- && ( blocksize != 4096L )
- && ( blocksize != 8192L )
- && ( blocksize != 16384L ))
- {
- printf ( "Illegal blocksize found: %ld\n", blocksize );
- exit ( 20 );
- }
- // Now scan for partitions.
- while (( (ULONG) sbb_Data - (ULONG) membuffer ) < sizememneeded )
- {
- if ( sbb_PB.pb_ID == IDNAME_PARTITION )
- {
- // We have one.
- if ( !handlePartition( sbb_Data, ffstype, blocksize ))
- {
- // Error attempting to fix partition
- exit( 20 );
- }
- }
- sbb_Data ++;
- }
- // OK, we're happy with the new RDBs - we hope.
- printf ( "Flush the old RDBs from hdwrench.library\n" );
- HDWCloseDevice ();
- deviceopen = HDWOpenDevice ( devicename, baseunit );
- if ( !deviceopen )
- {
- printf ( "No device was opened!\n");
- exit ( 20 );
- }
- rsuccess = InMemRDBStructs ( membuffer, // Start of RDB buffer
- sizememneeded, // Size of source buffer
- baseunit ); // Presumed unit
- if ( rsuccess == 0 )
- printf ( "RDB's successfully back in hdwrench.library\n" );
- else
- {
- printf ( "RDB's failed to load back into hdwrench.library %d\n", rsuccess );
- printf ( "We must stop here with RDBs mismatching the actual DosTypes.\n" );
- exit ( 20 );
- }
-
- // Write the file
- printf ( "\nWriting mountfile \"%s\"\n", filename );
- rsuccess = WriteMountfile ( filename, "sys:", baseunit );
- if ( rsuccess == 0 )
- printf ( "You should have a new %s waiting.\n", filename );
- else
- printf ( "MountFile write failed: %d\n", rsuccess );
- // And finally write back the RDBs to the disk
- printf ( "Writing RDBs to disk\n" );
- rwsuccess = WriteRDBs ( );
- if ( rwsuccess == 0 )
- printf ( "You should have a new RDBs waiting on the disk.\n" );
- else
- {
- if ( rwsuccess != 0xffff )
- printf ( "DOODOO CITY! RDB Write failed: %d\n", rwsuccess );
- else
- printf ( "RDB Write failed because this version does not have it supported.\n" );
- }
- }
- else
- {
- printf ( " Could not read the RDBs: %d\n", rsuccess );
- }
- }
- }
- else
- printf ( "Mountfile size write failed: %d\n", rsuccess );
- }
- else
- printf ( "InMemMountfile failed, %ld\n", rsuccess );
-
-
- cleanup:
-
- exit ( 0 );
- }
-
- void usage ( void )
- {
- printf ( "NoDirCache %s\n", TEMPLATE );
- printf ( "So I'm a stinker. Only device will default to scsi.device. You are\n" );
- printf ( "getting a freebie revised mountfile as well as an unDirCached disk\n" );
- printf ( "whether you want it or not. The TYPE parameter must be either \"FFS\"\n" );
- printf ( "or \"FS_INTL\".\n" );
- }
-
- int btrap ( void )
- {
- printf ( "\n***BREAK***\n" );
- exit(20);
- return 0;
- }
-
- void gone ( void )
- {
- if ( deviceopen )
- {
- printf ( "Closing opened device\n" );
- HDWCloseDevice();
- deviceopen = FALSE;
- }
-
- if ( membuffer )
- {
- free ( membuffer );
- membuffer = NULL;
- }
-
- if ( Args )
- FreeArgs ( Args );
-
- if ( HDWBase )
- CloseLibrary ( ( struct Library *) HDWBase );
- HDWBase = NULL;
- }
-
- BOOL handlePartition ( SmallBootBlock* sbb_Data, ULONG newDosType, ULONG blocksize )
- {
- struct DosEnvec* dev = (struct DosEnvec*) sbb_PB.pb_Environment;
- ULONG firstblock;
- USHORT ecode;
-
- // We have a partition block. Report type.
- printf ( "DosType = %lx found for partition %s:\n", dev->de_DosType, sbb_PB.pb_DriveName + 1 );
-
- // For testing porpoises...
- if (( dev->de_DosType == DIRCACHE )
- || ( dev->de_DosType == DIRCACHEI ))
- {
- BootBlock* bb = (BootBlock*) malloc( sizeof ( BootBlock ) + blocksize - 512 );
- // So fix it....
- if ( bb == NULL )
- {
- printf ( "Memory panic - out of memory!\n" );
- return FALSE;
- }
- // First change the RDB dostype
- printf ( " Fix RDB DosType\n" );
- dev->de_DosType = newDosType;
-
- firstblock = dev->de_LowCyl
- * dev->de_Surfaces
- * dev->de_BlocksPerTrack; // Real physical number....
- // Correct for old method of setting alternate logical block sizes.
- firstblock *= ( dev->de_SizeBlock << 2 ) / blocksize;
-
- // Now actually read firstblock;
- printf ( " Now read firstblock at %ld\n", firstblock );
- bb->bb_BlockNum = firstblock; // Only value really needed
- ecode = RawRead ( bb, blocksize );
- if ( ecode == success )
- {
- printf ( " DosType read is %lx\n", bb->bb_Data.bd_Longs [ 0 ] );
- bb->bb_Data.bd_Longs [ 0 ] = newDosType;
- ecode = RawWrite ( bb );
- if ( ecode != success )
- printf ( " !!!!Kiddo, for some reason the write back failed. You're in deep doodoo!\n" );
- else
- printf ( " Writeback succeeded\n" );
- }
-
- free( bb );
- }
- return TRUE;
- }
-